import 'log_level.dart';
import 'log_style_config.dart';
import 'log_rotation.dart';

/// 日志配置项，用于全局控制日志行为。
///
/// 使用 `PDLog.configure` 设置全局配置。常用选项：
/// - `enabled`：是否启用日志；
/// - `minLevel`：最小输出级别（低于该级别的日志会被忽略）；
/// - `defaultTag`：默认标签；
/// - `useConsole`：是否在 Dart 控制台打印；
/// - `showTimestamp`：是否在输出中加入时间戳。
///
/// 本地文件写入（Dart 管理）相关：
/// - `nativeFileLoggingEnabled`：是否开启本地文件写入（由 Dart 写入器处理）；
/// - `nativeFileLoggingFlushIntervalMs`：缓冲刷新间隔（毫秒）；
/// - `nativeFileLoggingMaxBufferEntries`：缓冲最大条目数；
/// - `nativeFileLoggingMaxBufferBytes`：缓冲最大字节数；
/// - `fileLoggingMinLevel`：写入文件的最小级别（低于该级别不写入文件）。
class PDLogConfig {
  final bool enabled;
  final LogLevel minLevel;
  final String? defaultTag;
  final bool useConsole;
  final bool showTimestamp;

  /// 是否启用 ANSI 颜色包裹（控制台/平台输出）。
  ///
  /// 关闭后所有输出均为纯文本，不包含 ANSI 转义码。
  final bool ansiEnabled;

  /// 是否在日志中显示调用者函数信息（通过解析调用栈获取）。
  ///
  /// 注意：启用该功能会带来一定的性能开销，建议仅在调试环境开启。
  final bool showCaller;

  /// 本地文件写入配置（Dart 管理）：是否启用与缓冲策略
  final bool nativeFileLoggingEnabled;
  final int nativeFileLoggingFlushIntervalMs; // 定时刷新间隔
  final int nativeFileLoggingMaxBufferEntries; // 最大缓冲条数
  final int nativeFileLoggingMaxBufferBytes; // 最大缓冲字节数

  /// 日志颜色样式配置（按级别设置前景色/背景色/样式）。
  final Map<LogLevel, LogStyleConfig> logStyles;

  /// 写入文件的最小级别阈值。
  ///
  /// 仅当开启了本地文件写入且日志级别不低于此值时，日志才会写入文件（由 Dart 写入器处理）。
  /// 典型设置为 `LogLevel.info`，从而只将 `info/warn/error` 持久化。
  final LogLevel fileLoggingMinLevel; // 文件写入最小级别

  /// 日志滚动策略（保留最近 N 天 / 月 / 年）。
  ///
  /// 默认 [LogRetentionStrategy.none] 表示不做滚动，所有日志永久保存。
  final LogRetentionStrategy logRetentionStrategy;

  /// 滚动保留的数量，按 `策略` 的单位解释：
  /// - 当策略为 `days` 时表示保留的天数；
  /// - 当策略为 `months` 时表示保留的月数；
  /// - 当策略为 `years` 时表示保留的年数。
  /// 当策略为 `none` 时该字段不生效。
  final int logRetentionCount;

  /// 文件事件去重窗口（毫秒）。
  ///
  /// 用于在短时间内抑制同一路径同类型的重复事件。
  /// 默认 500ms。
  final int fileEventDedupeWindowMs;

  /// 移动端文件轮询间隔（毫秒）。
  ///
  /// Android/iOS 使用轮询检测文件变化，默认 2000ms。
  final int mobileWatchPollingIntervalMs;

  const PDLogConfig({
    this.enabled = true,
    this.minLevel = LogLevel.verbose,
    this.defaultTag,
    this.useConsole = true,
    this.showTimestamp = false,
    this.ansiEnabled = false,
    this.showCaller = false,
    this.nativeFileLoggingEnabled = false,
    this.nativeFileLoggingFlushIntervalMs = 2000,
    this.nativeFileLoggingMaxBufferEntries = 100,
    this.nativeFileLoggingMaxBufferBytes = 64 * 1024,
    this.logStyles = kDefaultLogStyles,
    this.fileLoggingMinLevel = LogLevel.info,
    this.logRetentionStrategy = LogRetentionStrategy.none,
    this.logRetentionCount = 0,
    this.fileEventDedupeWindowMs = 500,
    this.mobileWatchPollingIntervalMs = 2000,
  });

  /// 复制当前配置并覆盖部分字段。
  PDLogConfig copyWith({
    bool? enabled,
    LogLevel? minLevel,
    String? defaultTag,
    bool? useConsole,
    bool? showTimestamp,
    bool? ansiEnabled,
    bool? showCaller,
    bool? nativeFileLoggingEnabled,
    int? nativeFileLoggingFlushIntervalMs,
    int? nativeFileLoggingMaxBufferEntries,
    int? nativeFileLoggingMaxBufferBytes,
    Map<LogLevel, LogStyleConfig>? logStyles,
    LogLevel? fileLoggingMinLevel, // 写文件的最小级别
    LogRetentionStrategy? logRetentionStrategy,
    int? logRetentionCount,
    int? fileEventDedupeWindowMs,
    int? mobileWatchPollingIntervalMs,
  }) {
    return PDLogConfig(
      enabled: enabled ?? this.enabled,
      minLevel: minLevel ?? this.minLevel,
      defaultTag: defaultTag ?? this.defaultTag,
      useConsole: useConsole ?? this.useConsole,
      showTimestamp: showTimestamp ?? this.showTimestamp,
      ansiEnabled: ansiEnabled ?? this.ansiEnabled,
      showCaller: showCaller ?? this.showCaller,
      nativeFileLoggingEnabled:
          nativeFileLoggingEnabled ?? this.nativeFileLoggingEnabled,
      nativeFileLoggingFlushIntervalMs: nativeFileLoggingFlushIntervalMs ??
          this.nativeFileLoggingFlushIntervalMs,
      nativeFileLoggingMaxBufferEntries: nativeFileLoggingMaxBufferEntries ??
          this.nativeFileLoggingMaxBufferEntries,
      nativeFileLoggingMaxBufferBytes: nativeFileLoggingMaxBufferBytes ??
          this.nativeFileLoggingMaxBufferBytes,
      logStyles: logStyles ?? this.logStyles,
      fileLoggingMinLevel: fileLoggingMinLevel ?? this.fileLoggingMinLevel,
      logRetentionStrategy: logRetentionStrategy ?? this.logRetentionStrategy,
      logRetentionCount: logRetentionCount ?? this.logRetentionCount,
      fileEventDedupeWindowMs:
          fileEventDedupeWindowMs ?? this.fileEventDedupeWindowMs,
      mobileWatchPollingIntervalMs:
          mobileWatchPollingIntervalMs ?? this.mobileWatchPollingIntervalMs,
    );
  }
}
